// 开启严格模式
'use strict';

/**
 * 初始化
 * @return void
 */
(function init() {
    // 数字
    number();
    // 日期
    date();
    // 侧边栏切换滑动(是否唯一)
    slideToggle(true);
    // 表格选择
    tableSelection();
})()

/**
 * 阻止冒泡
 * @param {Object} event 对象
 * @return void
 */
function stopBubbling(event) {
    event.stopPropagation ? event.stopPropagation() : window.event.cancelBubble = true;
}

/**
 * 数字
 * @return void
 */
function number() {
    // 数字
    var number = $('.number');

    // 监听值变化
    number.bind('input propertychange', function () {
        $(this).val($(this).val().replace(/[\D]/g, ''));
    })
}

/**
 * 日期
 * @return void
 */
function date() {
    // 日期
    var date = $('.date');

    // 监听值变化
    date.bind('input propertychange', function () {
        $(this).val($(this).val().replace(/[^0-9-]/g, ''));
    })
}

/**
 * 清除缓存
 * @param {String} url 地址
 * @return void
 */
function removeRuntime(url) {
    // 发送请求
    axios.get(url).then(function (res) {
        // 消息提示
        message('add', 'success', '清空缓存成功');
    }).catch(function (err) {
        // 消息提示
        message('add', 'error', err);
    })
}

/**
 * 设置模态框样式
 * @param {Object} wrap 包装
 * @param {Object} container 容器
 * @param {Boolean} isResize 是否监听窗口大小
 * @return void
 */
function setModelFrameStyle(wrap, container, isResize) {
    /**
     * 设置
     * @return void
     */
    function set() {
        // 可视区宽度
        var width = $(wrap).width();
        // 可视区高度
        var height = $(wrap).height();

        // 处理样式
        var left = (width - container.width()) / 2;
        var top = (height - container.height()) / 2;

        // 设置样式
        container.css({'left': left, 'top': top});
    }
    set();

    // 是否监听窗口大小
    if (isResize) {
        // 监听窗口大小
        $(window).resize(function () {
            set();
        })
    }
}

/**
 * 切换侧边栏
 * @param {Boolean} _this 当前元素
 * @return void
 */
function toggleSidebar(_this) {
    // 侧边栏
    var sidebar = $('aside');

    // 添加类名
    sidebar.toggleClass('hide');

    // 获取类名
    var className = sidebar.prop('class');

    // 更改属性
    className ? $(_this).prop('title', '展开侧边栏') : $(_this).prop('title', '收起侧边栏');
}

function articleOverflowY(operation) {
    // 独立内容容器
    var articleContainer = $('main article .container');

    // 设置样式
    articleContainer.css('overflow-y', operation);
}

/**
 * 显示模态框
 * @param {Type} wrap 包装
 * @param {Type} container 容器
 * @param {Boolean} isArticleOverflowY 是否隐藏Y轴滚动条
 * @return void
 */
function showModalFrame(wrap, container, header, isArticleOverflowY) {
    // 包装
    wrap = $(wrap);
    // 容器
    container = $(container);

    // 判断隐藏滚动条
    if (isArticleOverflowY) {
        // 独立内容容器
        var articleContainer = $('main article .container');
        // 滚动条顶部距离
        var scrollTop = articleContainer.scrollTop();

        // 隐藏滚动条
        articleOverflowY('hidden');

        // 设置样式
        wrap.css('top', scrollTop);
    }

    // 淡入
    wrap.stop().fadeIn(300);
    

    // 设置样式
    setModelFrameStyle(wrap, container, true);

    // 获取焦点
    var input = wrap.find('.model_frame-form-input');
    if (input.length) input.eq(0).focus();

    // 模态框拖拽(包装, 容器, 头部)
    modalFrameDrag(wrap, container, header);
}

/**
 * 隐藏模态框
 * @param {Type} event 对象
 * @param {Type} wrap 包装
 * @param {Boolean} isArticleOverflowY 是否显示Y轴滚动条
 * @return void
 */
function hideModalFrame(event, wrap, isArticleOverflowY) {
    // 阻止冒泡
    stopBubbling(event);

    // 判断显示滚动条
    if (isArticleOverflowY) articleOverflowY('auto');

    // 管理员信息框
    wrap = $(wrap);

    // 淡出
    wrap.stop().fadeOut(300);

    // 清空事件
    $(window).off();
}

/**
 * 切换模态框全屏
 * @param {Object} _this 当前元素
 * @param {Object} icon 图标
 * @return void
 */
function toggleModalFrameFullScreen(_this, icon) {
    if (arguments.length === 1) icon = _this;

    // 鼠标按下
    $(_this).mousedown(function () {
        // 阻止冒泡
        stopBubbling(event);
    })

    // 添加类名
    $(icon).toggleClass('fa-expand-arrows-alt fa-window-restore');
    $(icon).parents('.modal_frame-container').toggleClass('full_screen');
}

/**
 * 模态框拖拽
 * @param {Object} wrap 包装
 * @param {Object} container 容器
 * @param {Object} header 头部
 * @return void
 */
function modalFrameDrag(wrap, container, header) {
    // 包装
    wrap = $(wrap);
    // 容器
    container = $(container);
    // 头部
    header = $(header);
    // 按下左距离
    var downLeft = 0;
    // 按下上距离
    var downTop = 0;
    // 左距离
    var left = 0;
    // 上距离
    var top = 0;
    // 包装离左侧距离
    var offsetLeft = wrap.offset().left;
    // 包装离上侧距离
    var offsetTop = wrap.offset().top;

    /**
     * 鼠标按下
     * @return void
     */
    function mousedown() {
        // 鼠标按下
        header.mousedown(function (event) {
            // 阻止默认事件
            event.preventDefault();

            // 获取左距离
            downLeft = event.offsetX;
            // 获取上距离
            downTop = event.offsetY;
            
            /**
             * 鼠标移动
             * @return void
             */
            function mousemove() {
                // 鼠标移动
                $(document).mousemove(function (event) {
                    // 处理左距离
                    left = event.clientX - downLeft - offsetLeft <= 0 ? 0 : event.clientX - container.width() + container.width() - downLeft - offsetLeft;
                    left = wrap.width() - container.width() + offsetLeft <= event.clientX - downLeft ? wrap.width() - container.width() : left;
                    // 处理顶距离
                    top = event.clientY - downTop - offsetTop <= 0 ? 0 : event.clientY - container.height() + container.height() - downTop - offsetTop;
                    top = wrap.height() - container.height() + offsetTop <= event.clientY - downTop ? wrap.height() - container.height() : top;
                    // 设置样式
                    container.css({'left': left, 'top': top});
                })
            }
            mousemove();

            /**
             * 鼠标抬起
             * @return void
             */
            function mouseup() {
                // 鼠标抬起
                $(document).mouseup(function () {
                    // 清空事件
                    $(document).off();
                })
            }
            mouseup();
        })
    }
    mousedown();
}

/**
 * 侧边栏切换滑动
 * @param {Boolean} isOnly 是否唯一
 * @return void
 */
function slideToggle(isOnly) {
    // 活跃类名
    var ACTIVE = 'active';
    // 一级栏目
    var sidebarLink = $('.sidebar-link');
    // 二级栏目
    var sidebarLinkLink = $('.sidebar-link-link');

    // 一级点击
    sidebarLink.click(function () {
        // 是否唯一
        if (isOnly) {
            // 图标向左
            $(this).parent().siblings().find('.fa-chevron-down').toggleClass('fa-chevron-down fa-chevron-left');
            // 收起其他栏目
            $(this).parent().siblings().children('.sidebar-list-list').slideUp();
        }

        // 逻辑
        $(this).children('i:last-child').toggleClass('fa-chevron-left fa-chevron-down').parent().next().stop().slideToggle();
    })

    // 二级栏目点击
    sidebarLinkLink.click(function () {
        // 添加类名
        $(this).addClass(ACTIVE).parents('.sidebar-item').siblings().find('.sidebar-link-link').removeClass(ACTIVE);
    })
}

/**
 * 切换密码
 * @param {Object} _this 当前DOM
 * @return void
 */
function togglePassword(_this) {
    // 获取当前文本款类型
    var type = $(_this).prev().prop('type') === 'password' ? 'text' : 'password';
    // 获取当前标题值
    var title = $(_this).prop('title') === '查看密码' ? '隐藏密码' : '查看密码';

    // 切换类名
    $(_this).toggleClass('fa-eye fa-eye-slash').prop('title', title);

    // 切换类型
    $(_this).prev().prop('type', type);
}

/**
 * 表格选择
 * @return void
 */
function tableSelection() {
    // 活跃类名
    var active = 'active';
    // 类名
    var check = 'fa-check';
    var minus = 'fa-minus';
    // 全选按钮
    var selectAll = $('#select_all');
    // 数据按钮
    var tableTdSelection = $('.table-td-selection');

    /**
     * 全选反选
     * @return void
     */
    function SelectAllAndReverse() {
        selectAll.click(function () {
            // 获取当前状态
            var status = $(this).prop('checked');

            // 删除类名
            selectAll.next().removeClass(active).children().removeClass(minus).addClass(check);
    
            // 设置属性
            tableTdSelection.prop('checked', status);
        })
    }
    SelectAllAndReverse();

    /**
     * 监听数据选择
     * @return void
     */
    function MonitorDataSelection() {
        // 点击
        tableTdSelection.click(function () {
            // 获取选中数据
            var tableTdChooseData  = $('.table-td-selection:checked');

            // 判断
            var status = tableTdSelection.length === tableTdChooseData.length ? true : false;
            if (tableTdSelection.length !== tableTdChooseData.length && tableTdChooseData.length) {
                selectAll.next().addClass(active).children().addClass(minus).removeClass(check);
            } else if (tableTdChooseData.length === 0) {
                selectAll.next().removeClass(active);
            } else {
                selectAll.next().removeClass(active).children().removeClass(minus).addClass(check);
            }

            // 设置
            selectAll.prop('checked', status);
        })
    }
    MonitorDataSelection();
}

/**
 * 操作加载
 * @param {Object} obj DOM对象
 * @param {String} operation 操作
 * @param {String} type 类型
 * @return void
 */
// 旧元素i
var actionLoadingClssName = '';
function actionLoading(obj, operation, type) {
    // 加载
    var loadingClassName = 'fas fa-spinner fa-spin';

    // 判断操作
    switch (operation) {
        // 添加
        case 'add':
            // 禁用按钮
            $(obj).prop('disabled', true);
            // 设置样式
            $('html').css('cursor', 'progress');

            // 判断类型
            switch (type) {
                // 图标按钮
                case 'icon-btn':
                    // 设置样式
                    $(obj).css('opacity', .6);
                    // 获取元素i
                    var i = $(obj).children('i');
                    // 获取类名
                    actionLoadingClssName = i.prop('class');
                    // 添加加载
                    i.prop('class', loadingClassName);
                    break;
                // 按钮
                case 'btn':
                // Input
                case 'input':
                // 开关
                case 'switch':
                    // 设置样式
                    $(obj).next().css('opacity', .6);
                    // 添加加载
                    $(obj).after('<i class="' + loadingClassName + '"></i>');
                    break;
                // 图标
                case 'icon':
                    // 获取类名
                    actionLoadingClssName = $(obj).prop('class');
                    // 添加加载
                    $(obj).prop('class', loadingClassName);
                    break;
                // 提交
                case 'submit':
                    // 设置样式
                    $(obj).css('opacity', .6);
                    // 添加加载
                    $(obj).prepend('<i class="' + loadingClassName + '"></i>');
            }
            break;
        // 删除
        case 'remove':
            // 启用按钮
            $(obj).prop('disabled', false);
            // 设置样式
            $('html').css('cursor', 'auto');

            // 判断类型
            switch (type) {
                // 图标按钮
                case 'icon-btn':
                    // 设置样式
                    $(obj).css('opacity', 1);
                    // 删除加载
                    $(obj).children('i').prop('class', actionLoadingClssName);
                    break;
                // 按钮
                case 'btn':
                // Input
                case 'input':
                // 开关
                case 'switch':
                    // 删除加载
                    $(obj).next().remove();
                    // 设置样式
                    $(obj).next().css('opacity', 1);
                    break;
                // 图标
                case 'icon':
                    // 删除加载
                    $(obj).prop('class', actionLoadingClssName);
                    break;
                // 提交
                case 'submit':
                    // 设置样式
                    $(obj).css('opacity', 1);
                    // 删除加载
                    $(obj).children('i').remove();
            }
            break;
    }
}

/**
 * 消息提示
 * @param {String} operation 操作
 * @param {String} type 类型
 * @param {String} value 值
 * @return void
 */
// 消息定时器
var messageTimer = null;
function message(operation, type, value) {
    // 消息容器
    var messageWrap = $('#message-wrap');

    // 判断操作
    switch (operation) {
        case 'add':
            // 小图标类名
            var iconClassName = '';

            // 判断类型
            switch (type) {
                // 信息
                case 'info':
                    iconClassName = 'fas fa-info-circle';
                    break;
                // 成功
                case 'success':
                    iconClassName = 'fa-check-circle';
                    break;
                case '200':
                case 200:
                case '201':
                case 201:
                    iconClassName = 'fa-check-circle';
                    type = 'success';
                    break;
                // 警告
                case 'warning':
                    iconClassName = 'fa-exclamation-circle';
                    break;
                // 错误
                case 'error':
                    iconClassName = 'fa-times-circle';
                    break;
                case '404':
                case 404:
                    iconClassName = 'fa-check-circle';
                    type = 'error';
                    break;
            }

            // 消息
            var message = '<div class="' + type + '"><i class="fas ' + iconClassName + '"></i><p class="message-text">' + value + '</p><i class="fas fa-times" onclick="message(\'remove\')"></i></div>';

            // 添加消息
            messageWrap.append(message);

            // 延迟删除
            messageTimer = setTimeout(function () {
                // 删除消息
                messageWrap.children().eq(0).remove();
            }, 3000);
            break;
        case 'remove':
            // 清除定时器
            clearTimeout(messageTimer);

            // 删除消息
            messageWrap.children().eq(0).remove();
            break;
    }
}

/**
 * 确认框
 * @return void
 */
function confirmation(event, operation, confirmCallback, cancelCallback) {
    // 确认框
    var confirm = $('#confirm-wrap');

    // 判断操作
    switch (operation) {
        // 显示
        case 'show':
            // 容器
            var confirmContainer = $('.confirm-container');
            // 按钮
            var confirmBodyBtn = $('.confirm-body-btn');

            // 淡入
            confirm.stop().fadeIn(300);

            // 隐藏滚动条
            articleOverflowY('hidden');

            // 独立内容容器
            var articleContainer = $('main article .container');
            // 滚动条顶部距离
            var scrollTop = articleContainer.scrollTop();

            // 隐藏滚动条
            articleOverflowY('hidden');

            // 设置样式
            confirm.css('top', scrollTop);

            // 设置样式
            setModelFrameStyle(confirm, confirmContainer, true);

            // 拖拽
            modalFrameDrag(confirm, confirmContainer, '.confirm-header');

            
            /**
             * 点击
             * @return void
             */
            function click() {
                // 默认值
                if (!confirmCallback) confirmCallback = Function;
                if (!cancelCallback) cancelCallback = Function;

                // 点击
                confirmBodyBtn.off().click(function () {
                    // 获取值
                    var value = JSON.parse($(this).val());

                    // 判断
                    return value ? confirmCallback() : cancelCallback();
                })
            }
            click();
            break;
        // 隐藏
        case 'hide':
            // 阻止冒泡事件
            stopBubbling(event);

            // 淡出
            confirm.stop().fadeOut(300);

            // 显示滚动条
            articleOverflowY('auto');
            break;
    }
}

/**
 * 批量删除
 * @param {Object} _this 当前元素
 * @param {String} url 地址
 * @return void
 */
function bulkDeletion(_this, url) {
    // 获取选中数据
    var tableTdChooseData  = $('.table-td-selection:checked');

    if (tableTdChooseData.length) {
        // 显示确认框
        confirmation(event, 'show', function () {
            // 隐藏确认框
            confirmation(event, 'hide');

            // 添加加载
            actionLoading(_this, 'add', 'icon-btn');

            // ID
            var id = '';
            // 循环获取ID
            tableTdChooseData.each(function (index, item) {
                // 拼接ID
                id += index ? ',' + $(item).val() : $(item).val();
            })

            // 发送请求
            axios.delete(url + '/' + id).then(function (res) {
                // 消息提示
                message('add', res.data.type, res.data.message);

                // 删除加载
                actionLoading(_this, 'remove', 'icon-btn');

                // 判断是否删除成功
                if (res.data.state === 200) {
                    // 删除数据
                    tableTdChooseData.each(function (index, item) {
                        $('.table-tr-' + $(item).val()).remove();
                    })
                }
            }).catch(function (err) {
                // 消息提示
                message('add', 'error', err);

                // 删除加载
                actionLoading(_this, 'remove', 'icon-btn');
            })
        });
    } else {
        // 消息提示
        message('add', 'info', '请勾选需要删除的数据');
    }
}

/**
 * 排序
 * @param {Object} _this 当前DOM
 * @param {String} operation 操作
 * @param {String} url 地址
 * @return void
 */
var sortingValue = 0;
function sorting(_this, operation, url) {
    // 判断操作
    switch (operation) {
        case 'focus':
            // 保存值
            sortingValue = $(_this).val();
            break;
        case 'blur':
            // 获取值
            var value = $(_this).val();

            // 判断是否改变值
            if (value === sortingValue) return;

            // 添加加载
            actionLoading(_this, 'add', 'input');

            // 发送请求
            axios.put(url, {
                sorting: value
            }).then(function (res) {
                // 消息提示
                message('add', res.status, '排序成功');

                // 删除加载
                actionLoading(_this, 'remove', 'input');
            }).catch(function (err) {
                // 消息提示
                message('add', 'error', err);

                // 删除加载
                actionLoading(_this, 'remove', 'input');

                // 更改值
                $(_this).val(sortingValue);
            })
            break;
    }
}

 /**
  * 性别
  * @param {Object} _this 当前DOM
  * @param {String} url 地址
  * @return void
  */
function gender(_this, url) {
    // 获取当前状态
    var status = $(_this).prop('checked');

    // 添加加载
    actionLoading(_this, 'add', 'switch');

    // 发送请求
    axios.put(url, {
        gender: status
    }).then(function (res) {
        // 消息提示
        message('add', res.status, '更换性别成功');

        // 删除加载
        actionLoading(_this, 'remove', 'switch');
    }).catch(function (err) {
        // 消息提示
        message('add', 'error', err);

        // 删除加载
        actionLoading(_this, 'remove', 'switch');

        // 更改属性
        $(_this).prop('checked', !status);
    })
}

/**
 * 状态
 * @param {Object} _this 当前DOM
 * @param {String} url 地址
 * @return void
 */
function status(_this, url) {
    // 获取当前状态
    var status = $(_this).prop('checked');

    // 添加加载
    actionLoading(_this, 'add', 'btn');

    // 发送请求
    axios.put(url, {
        status: status
    }).then(function (res) {
        // 消息提示
        message('add', res.data.type, res.data.message);

        // 判断是否更新失败
        if (res.data.state === 401) {
            // 更改属性
            $(_this).prop('checked', !status);
        }

        // 删除加载
        actionLoading(_this, 'remove', 'btn');
    }).catch(function (err) {
        // 消息提示
        message('add', 'error', err);

        // 删除加载
        actionLoading(_this, 'remove', 'btn');

        // 更改属性
        $(_this).prop('checked', !status);
    })
}

/**
 * 放大图片
 * @param {String} src 路径
 * @return void
 */
function zoomInImage(src) {
    // 图片模态框
    var imageModalFrame = $('#image-modal_frame');
    // 图片
    var modalFrameBodyImage = $('.modal_frame-body-image');

    // 设置路径
    modalFrameBodyImage.prop('src', src);

    // 显示模态框
    showModalFrame(imageModalFrame);

    // 设置位置
    function setAddr() {
        // 处理
        var setLeft = ($(window).width() - modalFrameBodyImage.width()) / 2;
        var setTop = ($(window).height() - modalFrameBodyImage.height()) / 2;

        // 设置样式
        modalFrameBodyImage.css({left: setLeft, top: setTop});

        // 监听浏览器窗口
        $(window).resize(function () {
            // 处理
            setLeft = ($(window).width() - modalFrameBodyImage.width()) / 2;
            setTop = ($(window).height() - modalFrameBodyImage.height()) / 2;

            // 设置样式
            modalFrameBodyImage.css({left: setLeft, top: setTop});
        })
    }
    setAddr();

    // 拖拽
    function drag() {
        // 鼠标按下
        modalFrameBodyImage.mousedown(function (event) {
            // 阻止默认事件
            event.preventDefault();

            // 按下X
            var downX = event.offsetX;
            // 按下Y
            var downY = event.offsetY;
            // 左
            var left = 0;
            // 顶
            var top = 0;

            
            /**
             * 鼠标移动
             * @return void
             */
            function mousemove() {
                // 鼠标移动
                $(document).mousemove(function (event) {
                    // 处理左距离
                    left = event.clientX - downX <= 0 ? 0 : event.clientX - downX;
                    left = $(window).width() - modalFrameBodyImage.width() <= event.clientX - downX ? $(window).width() - modalFrameBodyImage.width() : left;
                    // 处理顶距离
                    top = event.clientY - downY <= 0 ? 0 : event.clientY - downY;
                    top = $(window).height() - modalFrameBodyImage.height() <= event.clientY - downY ? $(window).height() - modalFrameBodyImage.height() : top;

                    // 设置样式
                    modalFrameBodyImage.css({left: left, top: top});
                })
            }
            mousemove();

            /**
             * 鼠标抬起
             * @return void
             */
            function mouseup() {
                // 鼠标抬起
                $(document).mouseup(function () {
                    // 清空事件
                    $(document).off();
                })
            }
            mouseup();
        })
    }
    drag()
}